home *** CD-ROM | disk | FTP | other *** search
/ Mac Easy 2010 May / Mac Life Ubuntu.iso / casper / filesystem.squashfs / usr / lib / rhythmbox / plugins / jamendo / JamendoSource.pyc (.txt) < prev   
Encoding:
Python Compiled Bytecode  |  2009-04-20  |  15.8 KB  |  479 lines

  1. # Source Generated with Decompyle++
  2. # File: in.pyc (Python 2.6)
  3.  
  4. import rb
  5. import rhythmdb
  6. from JamendoSaxHandler import JamendoSaxHandler
  7. import JamendoConfigureDialog
  8. import os
  9. import gobject
  10. import gtk.glade as gtk
  11. import gnome
  12. import gconf
  13. import xml
  14. import gzip
  15. import datetime
  16. jamendo_song_info_uri = 'http://img.jamendo.com/data/dbdump_artistalbumtrack.xml.gz'
  17. mp32_uri = 'http://api.jamendo.com/get2/bittorrent/file/plain/?type=archive&class=mp32&album_id='
  18. ogg3_uri = 'http://api.jamendo.com/get2/bittorrent/file/plain/?type=archive&class=ogg3&album_id='
  19. stream_url = 'http://api.jamendo.com/get2/stream/track/redirect/?id=%s&streamencoding=ogg2'
  20. artwork_url = 'http://api.jamendo.com/get2/image/album/redirect/?id=%s&imagesize=200'
  21. artist_url = 'http://www.jamendo.com/get/artist/id/album/page/plain/'
  22. genre_id3 = [
  23.     'Blues',
  24.     'Classic Rock',
  25.     'Country',
  26.     'Dance',
  27.     'Disco',
  28.     'Funk',
  29.     'Grunge',
  30.     'Hip-Hop',
  31.     'Jazz',
  32.     'Metal',
  33.     'New Age',
  34.     'Oldies',
  35.     'Other',
  36.     'Pop',
  37.     'R&B',
  38.     'Rap',
  39.     'Reggae',
  40.     'Rock',
  41.     'Techno',
  42.     'Industrial',
  43.     'Alternative',
  44.     'Ska',
  45.     'Death Metal',
  46.     'Pranks',
  47.     'Soundtrack',
  48.     'Euro-Techno',
  49.     'Ambient',
  50.     'Trip-Hop',
  51.     'Vocal',
  52.     'Jazz+Funk',
  53.     'Fusion',
  54.     'Trance',
  55.     'Classical',
  56.     'Instrumental',
  57.     'Acid',
  58.     'House',
  59.     'Game',
  60.     'Sound Clip',
  61.     'Gospel',
  62.     'Noise',
  63.     'AlternRock',
  64.     'Bass',
  65.     'Soul',
  66.     'Punk',
  67.     'Space',
  68.     'Meditative',
  69.     'Instrumental Pop',
  70.     'Instrumental Rock',
  71.     'Ethnic',
  72.     'Gothic',
  73.     'Darkwave',
  74.     'Techno-Industrial',
  75.     'Electronic',
  76.     'Pop-Folk',
  77.     'Eurodance',
  78.     'Dream',
  79.     'Southern Rock',
  80.     'Comedy',
  81.     'Cult',
  82.     'Gangsta',
  83.     'Top 40',
  84.     'Christian Rap',
  85.     'Pop/Funk',
  86.     'Jungle',
  87.     'Native American',
  88.     'Cabaret',
  89.     'New Wave',
  90.     'Psychadelic',
  91.     'Rave',
  92.     'Showtunes',
  93.     'Trailer',
  94.     'Lo-Fi',
  95.     'Tribal',
  96.     'Acid Punk',
  97.     'Acid Jazz',
  98.     'Polka',
  99.     'Retro',
  100.     'Musical',
  101.     'Rock & Roll',
  102.     'Hard Rock',
  103.     'Folk',
  104.     'Folk-Rock',
  105.     'National Folk',
  106.     'Swing',
  107.     'Fast Fusion',
  108.     'Bebob',
  109.     'Latin',
  110.     'Revival',
  111.     'Celtic',
  112.     'Bluegrass',
  113.     'Avantgarde',
  114.     'Gothic Rock',
  115.     'Progressive Rock',
  116.     'Psychedelic Rock',
  117.     'Symphonic Rock',
  118.     'Slow Rock',
  119.     'Big Band',
  120.     'Chorus',
  121.     'Easy Listening',
  122.     'Acoustic',
  123.     'Humour',
  124.     'Speech',
  125.     'Chanson',
  126.     'Opera',
  127.     'Chamber Music',
  128.     'Sonata',
  129.     'Symphony',
  130.     'Booty Bass',
  131.     'Primus',
  132.     'Porn Groove',
  133.     'Satire',
  134.     'Slow Jam',
  135.     'Club',
  136.     'Tango',
  137.     'Samba',
  138.     'Folklore',
  139.     'Ballad',
  140.     'Power Ballad',
  141.     'Rhythmic Soul',
  142.     'Freestyle',
  143.     'Duet',
  144.     'Punk Rock',
  145.     'Drum Solo',
  146.     'Acapella',
  147.     'Euro-House',
  148.     'Dance Hall']
  149.  
  150. class JamendoSource(rb.BrowserSource):
  151.     __gproperties__ = {
  152.         'plugin': (rb.Plugin, 'plugin', 'plugin', gobject.PARAM_WRITABLE | gobject.PARAM_CONSTRUCT_ONLY) }
  153.     
  154.     def __init__(self):
  155.         rb.BrowserSource.__init__(self, name = _('Jamendo'))
  156.         self._JamendoSource__db = None
  157.         self._JamendoSource__saxHandler = None
  158.         self._JamendoSource__activated = False
  159.         self._JamendoSource__notify_id = 0
  160.         self._JamendoSource__update_id = 0
  161.         self._JamendoSource__info_screen = None
  162.         self._JamendoSource__updating = True
  163.         self._JamendoSource__load_current_size = 0
  164.         self._JamendoSource__load_total_size = 0
  165.         self._JamendoSource__db_load_finished = False
  166.         self._JamendoSource__catalogue_loader = None
  167.         self._JamendoSource__catalogue_check = None
  168.         self._JamendoSource__jamendo_dir = rb.find_user_cache_file('jamendo')
  169.         if os.path.exists(self._JamendoSource__jamendo_dir) is False:
  170.             os.makedirs(self._JamendoSource__jamendo_dir, 448)
  171.         
  172.         self._JamendoSource__local_catalogue_path = os.path.join(self._JamendoSource__jamendo_dir, 'dbdump.xml')
  173.         self._JamendoSource__local_catalogue_temp = os.path.join(self._JamendoSource__jamendo_dir, 'dbdump.xml.tmp')
  174.  
  175.     
  176.     def do_set_property(self, property, value):
  177.         if property.name == 'plugin':
  178.             self._JamendoSource__plugin = value
  179.         else:
  180.             raise AttributeError, 'unknown property %s' % property.name
  181.         return property.name == 'plugin'
  182.  
  183.     
  184.     def do_impl_get_browser_key(self):
  185.         return '/apps/rhythmbox/plugins/jamendo/show_browser'
  186.  
  187.     
  188.     def do_impl_get_paned_key(self):
  189.         return '/apps/rhythmbox/plugins/jamendo/paned_position'
  190.  
  191.     
  192.     def do_impl_pack_paned(self, paned):
  193.         self._JamendoSource__paned_box = gtk.VBox(False, 5)
  194.         self.pack_start(self._JamendoSource__paned_box)
  195.         self._JamendoSource__paned_box.pack_start(paned)
  196.  
  197.     
  198.     def do_impl_show_entry_popup(self):
  199.         self.show_source_popup('/JamendoSourceViewPopup')
  200.  
  201.     
  202.     def do_impl_get_ui_actions(self):
  203.         return [
  204.             'JamendoDownloadAlbum',
  205.             'JamendoDonateArtist']
  206.  
  207.     
  208.     def do_impl_get_status(self):
  209.         if self._JamendoSource__updating:
  210.             if self._JamendoSource__load_total_size > 0:
  211.                 progress = min(float(self._JamendoSource__load_current_size) / self._JamendoSource__load_total_size, 1)
  212.             else:
  213.                 progress = -1
  214.             return (_('Loading Jamendo catalogue'), None, progress)
  215.         qm = self.get_property('query-model')
  216.         return (qm.compute_status_normal('%d song', '%d songs'), None, 0)
  217.  
  218.     
  219.     def do_impl_activate(self):
  220.         if not self._JamendoSource__activated:
  221.             shell = self.get_property('shell')
  222.             self._JamendoSource__db = shell.get_property('db')
  223.             self._JamendoSource__entry_type = self.get_property('entry-type')
  224.             self._JamendoSource__activated = True
  225.             self._JamendoSource__show_loading_screen(True)
  226.             self._JamendoSource__update_id = gobject.timeout_add(21600000, self._JamendoSource__update_catalogue)
  227.             self._JamendoSource__update_catalogue()
  228.             sort_key = gconf.client_get_default().get_string(JamendoConfigureDialog.gconf_keys['sorting'])
  229.             if not sort_key:
  230.                 sort_key = 'Artist,ascending'
  231.             
  232.             self.get_entry_view().set_sorting_type(sort_key)
  233.         
  234.         rb.BrowserSource.do_impl_activate(self)
  235.  
  236.     
  237.     def do_impl_delete_thyself(self):
  238.         if self._JamendoSource__update_id != 0:
  239.             gobject.source_remove(self._JamendoSource__update_id)
  240.             self._JamendoSource__update_id = 0
  241.         
  242.         if self._JamendoSource__notify_id != 0:
  243.             gobject.source_remove(self._JamendoSource__notify_id)
  244.             self._JamendoSource__notify_id = 0
  245.         
  246.         if self._JamendoSource__catalogue_loader:
  247.             self._JamendoSource__catalogue_loader.cancel()
  248.             self._JamendoSource__catalogue_loader = None
  249.         
  250.         if self._JamendoSource__catalogue_check:
  251.             self._JamendoSource__catalogue_check.cancel()
  252.             self._JamendoSource__catalogue_check = None
  253.         
  254.         gconf.client_get_default().set_string(JamendoConfigureDialog.gconf_keys['sorting'], self.get_entry_view().get_sorting_type())
  255.         rb.BrowserSource.do_impl_delete_thyself(self)
  256.  
  257.     
  258.     def __catalogue_chunk_cb(self, result, total):
  259.         if not result or isinstance(result, Exception):
  260.             if result:
  261.                 print 'error loading catalogue: %s' % result
  262.             
  263.             self._JamendoSource__parser.close()
  264.             self._JamendoSource__db_load_finished = True
  265.             self._JamendoSource__updating = False
  266.             self._JamendoSource__load_db()
  267.             self._JamendoSource__show_loading_screen(False)
  268.             self._JamendoSource__catalogue_loader = None
  269.             return None
  270.         self._JamendoSource__parser.feed(result)
  271.         self._JamendoSource__load_current_size += len(result)
  272.         self._JamendoSource__load_total_size = total
  273.         self._JamendoSource__notify_status_changed()
  274.  
  275.     
  276.     def __load_catalogue(self):
  277.         print 'loading catalogue %s' % self._JamendoSource__local_catalogue_path
  278.         self._JamendoSource__notify_status_changed()
  279.         self._JamendoSource__db_load_finished = False
  280.         self._JamendoSource__saxHandler = JamendoSaxHandler()
  281.         self._JamendoSource__parser = xml.sax.make_parser()
  282.         self._JamendoSource__parser.setContentHandler(self._JamendoSource__saxHandler)
  283.         self._JamendoSource__catalogue_loader = rb.ChunkLoader()
  284.         self._JamendoSource__catalogue_loader.get_url_chunks(self._JamendoSource__local_catalogue_path, 65536, True, self._JamendoSource__catalogue_chunk_cb)
  285.  
  286.     
  287.     def __download_catalogue_chunk_cb(self, result, total, out):
  288.         if not result:
  289.             out.close()
  290.             catalog = gzip.open(self._JamendoSource__local_catalogue_temp)
  291.             out = open(self._JamendoSource__local_catalogue_path, 'w')
  292.             while True:
  293.                 s = catalog.read(4096)
  294.                 if s == '':
  295.                     break
  296.                 
  297.                 out.write(s)
  298.             out.close()
  299.             catalog.close()
  300.             os.unlink(self._JamendoSource__local_catalogue_temp)
  301.             self._JamendoSource__db_load_finished = True
  302.             self._JamendoSource__show_loading_screen(False)
  303.             self._JamendoSource__catalogue_loader = None
  304.             self._JamendoSource__load_catalogue()
  305.         elif isinstance(result, Exception):
  306.             pass
  307.         else:
  308.             out.write(result)
  309.             self._JamendoSource__load_current_size += len(result)
  310.             self._JamendoSource__load_total_size = total
  311.         self._JamendoSource__notify_status_changed()
  312.  
  313.     
  314.     def __download_catalogue(self):
  315.         print 'downloading catalogue'
  316.         self._JamendoSource__updating = True
  317.         out = open(self._JamendoSource__local_catalogue_temp, 'w')
  318.         self._JamendoSource__catalogue_loader = rb.ChunkLoader()
  319.         self._JamendoSource__catalogue_loader.get_url_chunks(jamendo_song_info_uri, 4096, True, self._JamendoSource__download_catalogue_chunk_cb, out)
  320.  
  321.     
  322.     def __update_catalogue(self):
  323.         
  324.         def update_cb(result):
  325.             self._JamendoSource__catalogue_check = None
  326.             if result is True:
  327.                 self._JamendoSource__download_catalogue()
  328.             elif self._JamendoSource__db_load_finished is False:
  329.                 self._JamendoSource__load_catalogue()
  330.             
  331.  
  332.         self._JamendoSource__catalogue_check = rb.UpdateCheck()
  333.         self._JamendoSource__catalogue_check.check_for_update(self._JamendoSource__local_catalogue_path, jamendo_song_info_uri, update_cb)
  334.  
  335.     
  336.     def __show_loading_screen(self, show):
  337.         if self._JamendoSource__info_screen is None:
  338.             gladexml = gtk.glade.XML(self._JamendoSource__plugin.find_file('jamendo-loading.glade'), root = 'jamendo_loading_scrolledwindow')
  339.             self._JamendoSource__info_screen = gladexml.get_widget('jamendo_loading_scrolledwindow')
  340.             self.pack_start(self._JamendoSource__info_screen)
  341.             self.get_entry_view().set_no_show_all(True)
  342.             self._JamendoSource__info_screen.set_no_show_all(True)
  343.         
  344.         self._JamendoSource__info_screen.set_property('visible', show)
  345.         self._JamendoSource__paned_box.set_property('visible', not show)
  346.  
  347.     
  348.     def __load_db(self):
  349.         artists = self._JamendoSource__saxHandler.artists
  350.         nbAlbums = 0
  351.         nbTracks = 0
  352.         for artist_key in artists.keys():
  353.             artist = artists[artist_key]
  354.             for album_key in artist['ALBUMS'].keys():
  355.                 nbAlbums = nbAlbums + 1
  356.                 album = artist['ALBUMS'][album_key]
  357.                 for track_key in album['TRACKS'].keys():
  358.                     nbTracks = nbTracks + 1
  359.                     track = album['TRACKS'][track_key]
  360.                     track_id = track['id']
  361.                     stream = stream_url % track_id
  362.                     entry = self._JamendoSource__db.entry_lookup_by_location(stream)
  363.                     if entry == None:
  364.                         entry = self._JamendoSource__db.entry_new(self._JamendoSource__entry_type, stream)
  365.                     
  366.                     release_date = album['releasedate']
  367.                     if release_date:
  368.                         year = int(release_date[0:4])
  369.                         date = datetime.date(year, 1, 1).toordinal()
  370.                         self._JamendoSource__db.set(entry, rhythmdb.PROP_DATE, date)
  371.                     
  372.                     self._JamendoSource__db.set(entry, rhythmdb.PROP_TITLE, track['name'])
  373.                     self._JamendoSource__db.set(entry, rhythmdb.PROP_ARTIST, artist['name'])
  374.                     
  375.                     try:
  376.                         genre = genre_id3[int(album['id3genre'])]
  377.                     except Exception:
  378.                         genre = _('Unknown')
  379.  
  380.                     self._JamendoSource__db.set(entry, rhythmdb.PROP_GENRE, genre)
  381.                     self._JamendoSource__db.set(entry, rhythmdb.PROP_ALBUM, album['name'])
  382.                     trackno = int(track['numalbum'])
  383.                     if trackno >= 0:
  384.                         self._JamendoSource__db.set(entry, rhythmdb.PROP_TRACK_NUMBER, trackno)
  385.                     
  386.                     
  387.                     try:
  388.                         duration = float(track['duration'])
  389.                         self._JamendoSource__db.set(entry, rhythmdb.PROP_DURATION, int(duration))
  390.                     except Exception:
  391.                         pass
  392.  
  393.                     self._JamendoSource__db.set(entry, rhythmdb.PROP_MUSICBRAINZ_ALBUMID, album['id'])
  394.                 
  395.             
  396.         
  397.         print 'Nb artistes : ' + str(len(artists))
  398.         print 'Nb albums : ' + str(nbAlbums)
  399.         print 'Nb tracks : ' + str(nbTracks)
  400.         self._JamendoSource__db.commit()
  401.         self._JamendoSource__saxHandler = None
  402.  
  403.     
  404.     def __notify_status_changed(self):
  405.         
  406.         def change_idle_cb():
  407.             self.notify_status_changed()
  408.             self._JamendoSource__notify_id = 0
  409.             return False
  410.  
  411.         if self._JamendoSource__notify_id == 0:
  412.             self._JamendoSource__notify_id = gobject.idle_add(change_idle_cb)
  413.         
  414.  
  415.     
  416.     def download_album(self):
  417.         tracks = self.get_entry_view().get_selected_entries()
  418.         format = gconf.client_get_default().get_string(JamendoConfigureDialog.gconf_keys['format'])
  419.         if not format or format not in JamendoConfigureDialog.format_list:
  420.             format = 'ogg3'
  421.         
  422.         if len(tracks) == 1:
  423.             track = tracks[0]
  424.             albumid = self._JamendoSource__db.entry_get(track, rhythmdb.PROP_MUSICBRAINZ_ALBUMID)
  425.             formats = { }
  426.             formats['mp32'] = mp32_uri + albumid
  427.             formats['ogg3'] = ogg3_uri + albumid
  428.             p2plink = formats[format]
  429.             l = rb.Loader()
  430.             l.get_url(p2plink, self._JamendoSource__download_p2plink, albumid)
  431.         
  432.  
  433.     
  434.     def __download_p2plink(self, result, albumid):
  435.         if result is None:
  436.             emsg = _('Error looking up p2plink for album %s on jamendo.com') % albumid
  437.             gtk.MessageDialog(None, 0, gtk.MESSAGE_INFO, gtk.BUTTONS_OK, emsg).run()
  438.             return None
  439.         rb.show_uri(result)
  440.  
  441.     
  442.     def launch_donate(self):
  443.         tracks = self.get_entry_view().get_selected_entries()
  444.         if len(tracks) == 1:
  445.             track = tracks[0]
  446.             albumid = self._JamendoSource__db.entry_get(track, rhythmdb.PROP_MUSICBRAINZ_ALBUMID)
  447.             artist = self._JamendoSource__db.entry_get(track, rhythmdb.PROP_ARTIST)
  448.             url = artist_url + albumid.__str__() + '/'
  449.             l = rb.Loader()
  450.             l.get_url(url, self._JamendoSource__open_donate, artist)
  451.         
  452.  
  453.     
  454.     def __open_donate(self, result, artist):
  455.         if result is None:
  456.             emsg = _('Error looking up artist %s on jamendo.com') % artist
  457.             gtk.MessageDialog(None, 0, gtk.MESSAGE_INFO, gtk.BUTTONS_OK, emsg).run()
  458.             return None
  459.         rb.show_uri(result + 'donate/')
  460.  
  461.     
  462.     def playing_entry_changed(self, entry):
  463.         if not (self._JamendoSource__db) or not entry:
  464.             return None
  465.         if entry.get_entry_type() != self._JamendoSource__db.entry_type_get_by_name('JamendoEntryType'):
  466.             return None
  467.         gobject.idle_add(self.emit_cover_art_uri, entry)
  468.  
  469.     
  470.     def emit_cover_art_uri(self, entry):
  471.         stream = self._JamendoSource__db.entry_get(entry, rhythmdb.PROP_LOCATION)
  472.         albumid = self._JamendoSource__db.entry_get(entry, rhythmdb.PROP_MUSICBRAINZ_ALBUMID)
  473.         url = artwork_url % albumid
  474.         self._JamendoSource__db.emit_entry_extra_metadata_notify(entry, 'rb:coverArt-uri', str(url))
  475.         return False
  476.  
  477.  
  478. gobject.type_register(JamendoSource)
  479.